package plugin.demo.apt.processor;

import com.google.auto.service.AutoService;
import com.squareup.javapoet.MethodSpec;
import com.squareup.javapoet.TypeSpec;
import plugin.demo.apt.annotations.Print;

import javax.annotation.processing.*;
import javax.lang.model.SourceVersion;
import javax.lang.model.element.*;
import javax.lang.model.util.Elements;
import javax.lang.model.util.Types;
import javax.tools.Diagnostic;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
import java.util.stream.Collectors;

/**
 * @Author: Qiao Hang
 * @CreateDate: 2021/5/13 下午2:30
 * @UpdateDate:
 * @Description:
 */
@AutoService(javax.annotation.processing.Processor.class)
public class PrintProcessor extends AbstractProcessor{

    private Filer filer;
    private Elements elements;
    private Types types;
    private Messager messager;

    @Override
    public synchronized void init(ProcessingEnvironment processingEnv) {
        super.init(processingEnv);
        this.filer = processingEnv.getFiler();
        this.elements = processingEnv.getElementUtils();
        this.types = processingEnv.getTypeUtils();
        this.messager = processingEnv.getMessager();
    }

    @Override
    public SourceVersion getSupportedSourceVersion() {
        return SourceVersion.latestSupported();
    }

    @Override
    public Set<String> getSupportedAnnotationTypes() {
        Set<String> supportAnnotationTypes = new HashSet<>();
        supportAnnotationTypes.add(Print.class.getName());
        return supportAnnotationTypes;
    }

    @Override
    public boolean process(Set<? extends TypeElement> annotations, RoundEnvironment roundEnv) {
        //获取所有被Print标注的类
        Set<? extends Element> annotatedWith = roundEnv.getElementsAnnotatedWith(Print.class);

        for (Element element : annotatedWith) {
            switch (element.getKind()){
                case METHOD:
                    ExecutableElement method = (ExecutableElement) element;
                    TypeElement parentElement = (TypeElement) element.getEnclosingElement();
                    this.messager.printMessage(Diagnostic.Kind.NOTE,"digest method: " + parentElement.getQualifiedName() + "." +  method.getSimpleName());
            }
        }

        //该方法返回ture表示该注解已经被处理, 后续不会再有其他处理器处理; 返回false表示仍可被其他处理器处理.
        return true;
    }
}